Java进阶-- volatile关键字

volatile含有部分synchronized的特性,效率更高,但使用时需要注意细节,不然容易出错

是什么

Java中被volatile修饰的变量,每次读写都会直接使用“内存”介质,而不是使用CPU缓存

音 — UK /ˈvɒl.ə.taɪl/ US /ˈvɑː.lə.t̬əl/

英 — likely to change suddenly and unexpectedly or suddenly become violent or angry

中 — 易变的

特性

  • 保证变量可见性
  • 禁止指令进行重排序

基础概念:可见性、有序性、原子性

  1. 可见性:对所有线程来说,任一线程对变量的改动都立即可见
  2. 有序性:代码可能会被编译器混编,有序性即指代码按顺序执行
  3. 原子性:所有操作不会被打断,谁也不行(除非断电)

实际上我们对变量的修改,虽然可能Java就一行代码(如 y=x),但被解释成汇编语言会变成多行(y=x就需要进行两步操作:读x值,写入y所在内存,学过汇编的同学应该比较清楚)

与synchronized的区别

按字面理解,volatile关键字只是标记变量为易变的,并不能保证对变量的所有操作都是同步的,即不能保证具有synchronized一样的效果

实际上,对volatile修饰的变量的读/写操作是可以保证其原子性的,但还要注意一个问题,即同时写变量的线程可能不止一个,如此一来,其中部分的写操作就有可能丢失

听起来好像volatile使用起来很危险,但它也是有它的用途的

用法

  • 对于写不依赖历史状态的变量,可以考虑使用volatile修饰字代替synchronized来提高程序效率
  • 保证代码的有序性:volatile变量的读写操作之前的代码,编译器是不会进行重排序的

小结

在volatile满足不了要求的场景可以考虑使用synchronized、lock、Atomic变量来保证特性

对变量的写不依赖历史状态的变量使用volatile修饰可以提高效率

对于需要保证部分程序语句有序性的场景可以考虑使用volatile代替锁定整个代码块,提高效率

Powered by KyleCe

Copyright © 2015 - 2019 KyleCe All Rights Reserved.

访客数 : | 访问量 :